﻿using System;
using System.Collections.Generic;
using System.Text;
using System.IO;

namespace agvcontroller.Log
{
    public enum enumLogLevel
    {
        DEBUG,
        INFO,
        ERROR,
        WARNING,
        EXCEPTION,
    }

    public enum enumCategory
    {
        DRIVER,
        MODULE,
        GUI,
        SIMULATOR,
    }

    public delegate void deleLogDisplay(object sender , string msg , enumLogLevel level);

    public class Logger
    {
        public static event deleLogDisplay onDisplayLog;

        public static readonly string LogPath = @".\Log\";
        
        protected string _LogName;
        public string LogName
        {
            get
            {
                return _LogName;
            }
        }

        public Logger(string _Name)
        {
            _LogName = _Name;
        }

        public string GetBaseLog()
        {
            return string.Format("[{0}] [{1}] ", DateTime.Now.ToString("HH:mm:ss.mmm"), _LogName);
        }

        public void LogMsg(string msg, enumLogLevel level)
        {
            switch (level)
            {
                case enumLogLevel.DEBUG:
                    Debug(msg);
                    break;
                case enumLogLevel.INFO:
                    Info(msg);
                    break;
                case enumLogLevel.ERROR:
                    Error(msg);
                    break;
                case enumLogLevel.WARNING:
                    break;
                case enumLogLevel.EXCEPTION:
                    break;
            }
        }

        public void Debug(string _msg)
        {
            string log = GetBaseLog() + "[Debug] " + _msg;
            Log(log);

            if (onDisplayLog != null)
                onDisplayLog(this, log, enumLogLevel.DEBUG);
        }

        public void Info(string _msg)
        {
            string log = GetBaseLog() + "[Info] " + _msg;
            Log(GetBaseLog() + "[Info] " + _msg);

            if (onDisplayLog != null)
                onDisplayLog(this, log, enumLogLevel.INFO);
        }

        public void Error(string _msg, bool display = false)
        {
            string log = GetBaseLog() + "[Error] " + _msg;
            Log(GetBaseLog() + "[Error] " + _msg);

            if (onDisplayLog != null)
                onDisplayLog(this, log, enumLogLevel.ERROR);
        }

        public void Exception(string _msg, bool display = false)
        {
            string log = GetBaseLog() + "[Exception] " + _msg;
            Log(GetBaseLog() + "[Exception] " + _msg);

            if (onDisplayLog != null)
                onDisplayLog(this, log, enumLogLevel.EXCEPTION);
        }

        private void Log(string msg, bool display=false)
        {
            FileStream _fileStream = null;
            StreamWriter _streamWriter = null;

            try
            {
                string strFileName = GetFileName();
                if (string.IsNullOrEmpty(strFileName)) return;

                if (_streamWriter != null)
                    _streamWriter.Close();

                if (_fileStream != null)
                    _fileStream.Close();

                _fileStream = new FileStream(strFileName, FileMode.Append, FileAccess.Write, FileShare.ReadWrite);
                _streamWriter = new StreamWriter(_fileStream);
                _streamWriter.AutoFlush = true;

                if (_streamWriter != null)
                    _streamWriter.WriteLine("{0}", msg);

                if (_streamWriter != null)
                    _streamWriter.Close();

                if (_fileStream != null)
                    _fileStream.Close();
            }
            catch (IOException ex)
            {
                if (_streamWriter != null)
                    _streamWriter.Close();

                if (_fileStream != null)
                    _fileStream.Close();
            }
            
            return;
        }

        public void Close()
        {
        }

        protected virtual string GetFileName()
        {
            if (!Directory.Exists(LogPath + LogName))
                Directory.CreateDirectory(LogPath+LogName);

            string strFileName = LogName + "_" + DateTime.Now.ToString("MM-dd") + ".log";
            return Path.Combine(LogPath+LogName, strFileName);
        }
    }
}
